import configparser
import csv
import os

import numpy as np

from constants import *

with open(f"{DATA_DIR}/demand.csv", mode='rt', encoding='UTF-8') as _r:
    _reader = csv.reader(_r)
    _header = next(_reader)
    client_names = _header[1:]  # 去除时间列
    _demand_list = []
    for _row in _reader:
        _row = _row[1:]  # 去除时间列
        _row = list(map(int, _row))
        _demand_list.append(_row)
    demand_matrix = np.array(_demand_list)


with open(f"{DATA_DIR}/site_bandwidth.csv", mode='rt', encoding='UTF-8') as _r:
    _reader = csv.reader(_r)
    site_names = []
    _site_bandwidth_list = []
    next(_reader)  # 去除表头
    for _site_name, _bandwidth in _reader:
        site_names.append(_site_name)
        _site_bandwidth_list.append(int(_bandwidth))
    site_bandwidth_arr = np.array(_site_bandwidth_list)

M = len(client_names)
N = len(site_names)
T = demand_matrix.shape[0]
client_name_2_index = dict(zip(client_names, range(M)))
site_name_2_index = dict(zip(site_names, range(N)))
quantile_index = int(np.ceil(QUANTILE * T) - 1)  # 从0开始计数，因此坐标减1

_config = configparser.RawConfigParser()
_config.read(f"{DATA_DIR}/config.ini", encoding='UTF-8')
qos_constraint = _config.getint('config', 'qos_constraint')

with open(f"{DATA_DIR}/qos.csv", mode='rt', encoding='UTF-8') as _r:
    _reader = csv.DictReader(_r)
    reachable_matrix = np.zeros(shape=(M, N), dtype=np.int64)

    for _row in _reader:
        _site_name = _row['site_name']
        _site_id = site_name_2_index[_site_name]
        for _client_id, _client_name in enumerate(client_names):
            _qos = int(_row[_client_name])
            if _qos < qos_constraint:
                reachable_matrix[_client_id, _site_id] = 1


def _to_output_str(assign_matrix):
    output_str = ""
    for client_id, client_name in enumerate(client_names):
        client_assign_arr = assign_matrix[client_id, :]
        client_assign_str = ','.join(f"<{site_names[si]},{client_assign_arr[si]}>" for si in np.argwhere(client_assign_arr).flatten())
        output_str += f"{client_name}:{client_assign_str}\n"
    return output_str


def output(assigner):
    os.makedirs(os.path.dirname(OUTPUT_FILE), exist_ok=True)
    with open(OUTPUT_FILE, mode='wt', encoding='UTF-8') as _w:
        for t in range(T):
            assign_matrix = assigner.next_assign()
            output_str = _to_output_str(assign_matrix)
            if t == (assigner.T - 1):
                output_str = output_str[:-1]  # 去除结尾多余的换行符
            _w.write(output_str)
